package handlers

import (
	"net/http"

	"context"
	"strconv"
	"time"
	"wardrobe-server/data"
	models "wardrobe-server/models"

	"github.com/gin-gonic/gin"
)

// RegisterWardrobeRoutes sets up wardrobe-related routes on the given router group or engine.
func RegisterWardrobeRoutes(r *gin.Engine) {
	r.GET("/api/wardrobes", func(c *gin.Context) {
		ctx := context.Background()
		list, err := data.ListWardrobes(ctx)
		if err != nil {
			c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
			return
		}
		c.JSON(http.StatusOK, list)
	})

	// 详情视图
	r.GET("/api/wardrobes/:id", func(c *gin.Context) {
		id, _ := strconv.Atoi(c.Param("id"))
		ctx := context.Background()
		detail, err := data.GetDetailedWardrobe(ctx, id)
		if err != nil {
			c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
			return
		}
		c.JSON(http.StatusOK, detail)
	})

	// 1) 待拆 - 创建衣柜 + 媒体 + 初始费用
	r.POST("/api/wardrobes/disassembly", func(c *gin.Context) {
		var req models.DisassemblyCreateRequest
		if err := c.ShouldBindJSON(&req); err != nil {
			c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})
			return
		}
		ctx := context.Background()
		w := models.Wardrobe{
			Code:     req.Code,
			Name:     req.Name,
			Status:   "pending_disassembly",
			Location: req.Location,
			Specs:    req.Specs,
			BuyPrice: req.BuyPrice,
		}
		saved, err := data.InsertWardrobe(ctx, w)
		if err != nil {
			c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
			return
		}
		if err := data.InsertMediaBatch(ctx, saved.ID, "disassembly", "image", req.Images); err != nil {
			c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
			return
		}
		if err := data.InsertMediaBatch(ctx, saved.ID, "disassembly", "video", req.Videos); err != nil {
			c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
			return
		}
		if req.ParkingFee > 0 {
			_ = data.InsertExpense(ctx, models.Expense{WardrobeID: saved.ID, Stage: "disassembly", Category: "parking_fee", Amount: req.ParkingFee})
		}
		if req.LaborFee > 0 {
			_ = data.InsertExpense(ctx, models.Expense{WardrobeID: saved.ID, Stage: "disassembly", Category: "labor_fee", Amount: req.LaborFee})
		}
		c.JSON(http.StatusCreated, saved)
	})

	// 2) 待上架 - 编辑媒体，设置售卖信息
	r.PUT("/api/wardrobes/:id/listing", func(c *gin.Context) {
		id, _ := strconv.Atoi(c.Param("id"))
		var req models.ListingUpdateRequest
		if err := c.ShouldBindJSON(&req); err != nil {
			c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})
			return
		}
		ctx := context.Background()
		if err := data.UpdateListing(ctx, id, req.SalePrice, req.Description); err != nil {
			c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
			return
		}
		if len(req.Images) > 0 {
			_ = data.InsertMediaBatch(ctx, id, "listing", "image", req.Images)
		}
		if len(req.Videos) > 0 {
			_ = data.InsertMediaBatch(ctx, id, "listing", "video", req.Videos)
		}
		c.JSON(http.StatusOK, gin.H{"ok": true})
	})

	// 3) 已上架
	r.PUT("/api/wardrobes/:id/listed", func(c *gin.Context) {
		id, _ := strconv.Atoi(c.Param("id"))
		ctx := context.Background()
		if err := data.SetStatus(ctx, id, "listed"); err != nil {
			c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
			return
		}
		c.JSON(http.StatusOK, gin.H{"ok": true})
	})

	// 4) 待安装 - 记录订单和安装信息
	r.PUT("/api/wardrobes/:id/installation", func(c *gin.Context) {
		id, _ := strconv.Atoi(c.Param("id"))
		var req models.InstallationUpsertRequest
		if err := c.ShouldBindJSON(&req); err != nil {
			c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})
			return
		}
		parseTime := func(s string) time.Time { t, _ := time.Parse(time.RFC3339, s); return t }
		info := models.InstallationInfo{
			WardrobeID:    id,
			OrderTime:     parseTime(req.OrderTimeISO),
			CustomerName:  req.CustomerName,
			CustomerPhone: req.CustomerPhone,
			Address:       req.Address,
			HasElevator:   req.HasElevator,
			InstallTime:   parseTime(req.InstallTimeISO),
			Notes:         req.Notes,
		}
		ctx := context.Background()
		if err := data.UpsertInstallation(ctx, info); err != nil {
			c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
			return
		}
		_ = data.SetStatus(ctx, id, "pending_installation")
		c.JSON(http.StatusOK, gin.H{"ok": true})
	})

	// 5) 待结账 - 记录费用
	r.POST("/api/wardrobes/:id/settlement", func(c *gin.Context) {
		id, _ := strconv.Atoi(c.Param("id"))
		var req models.SettlementRequest
		if err := c.ShouldBindJSON(&req); err != nil {
			c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})
			return
		}
		ctx := context.Background()
		if req.LaborFee > 0 {
			_ = data.InsertExpense(ctx, models.Expense{WardrobeID: id, Stage: "settlement", Category: "labor_fee", Amount: req.LaborFee})
		}
		if req.ParkingFee > 0 {
			_ = data.InsertExpense(ctx, models.Expense{WardrobeID: id, Stage: "settlement", Category: "parking_fee", Amount: req.ParkingFee})
		}
		if req.MileageElectricity > 0 {
			_ = data.InsertExpense(ctx, models.Expense{WardrobeID: id, Stage: "settlement", Category: "mileage_electricity", Amount: req.MileageElectricity})
		}
		if req.MealsFee > 0 {
			_ = data.InsertExpense(ctx, models.Expense{WardrobeID: id, Stage: "settlement", Category: "meals", Amount: req.MealsFee})
		}
		if req.PlatformFee > 0 {
			_ = data.InsertExpense(ctx, models.Expense{WardrobeID: id, Stage: "settlement", Category: "platform_fee", Amount: req.PlatformFee})
		}
		if req.PayoutInstaller > 0 {
			_ = data.InsertExpense(ctx, models.Expense{WardrobeID: id, Stage: "settlement", Category: "payout_installer", Amount: req.PayoutInstaller})
		}
		_ = data.SetStatus(ctx, id, "pending_archive")
		c.JSON(http.StatusOK, gin.H{"ok": true})
	})

	// 6) 存档
	r.PUT("/api/wardrobes/:id/archive", func(c *gin.Context) {
		id, _ := strconv.Atoi(c.Param("id"))
		ctx := context.Background()
		if err := data.SetStatus(ctx, id, "archived"); err != nil {
			c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
			return
		}
		c.JSON(http.StatusOK, gin.H{"ok": true})
	})
}
